home *** CD-ROM | disk | FTP | other *** search
/ Turnbull China Bikeride / Turnbull China Bikeride - Disc 1.iso / ARGONET / PD / PROGRAMMING / DESKLIBC / SOURCES.ZIP / DeskLib / !DLSources / Libraries / Icon / c / Slider < prev    next >
Text File  |  1995-07-08  |  8KB  |  200 lines

  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <string.h>
  4.  
  5. #include "DeskLib:Wimp.h"
  6. #include "DeskLib:WimpSWIs.h"
  7. #include "DeskLib:Coord.h"
  8. #include "DeskLib:Icon.h"
  9.  
  10.  
  11. /* ==========================================================================
  12.    Icon_Slider:
  13.    This is a draggable "volume bar" as in the task window memory displays.
  14.    It consists of two icons, a "base" icon, which provides
  15.      a) a pretty border for the slider (indented plinth) if you want it.
  16.      b) a simple, tidy, and effective means of setting the bounds within
  17.         which the slider can be dragged. Note that this also means that the
  18.         slider can easily be resized just by changing the template
  19.         definition of the icons.
  20.  
  21.    ...and a "slider" icon, which defines:
  22.      a) The type of icon used. Currently slider only provides a
  23.         "left-end-fixed, right-end draggable" style slider, in which cse you
  24.         specify the size, y-position, and colours of the icon. Later I might
  25.         get around to writing code to handle a fixed-size moving icon (so
  26.         you can have a "volume knob" that moves rather than a "bar graph")
  27.      b) The y-position of the icon (X positions are read from the base icon)
  28.         and the left hand end position of the icon.
  29.  
  30.      As the slider is dragged (or indeed at any time) a value is read from
  31.      the slider in the form of an integer. When the slider is at a
  32.      minimum size, 0 is returned; at maximum, 1000 is returned.
  33.  
  34.      The base icon should have a LOWER icon handle than the slider (so the
  35.      slider appears on top)
  36.      When either icon is clicked, initiate the drag with DragSlider, then
  37.      continuously update by repeatedly calling UpdateSlider on NULL (or
  38.      perhaps button if buttontype == always) events.
  39.      At any time, the current slider value can be read using ReadSlider.
  40.  
  41.      All these calls return the current slider position, so that you may
  42.      update other displays (for example, alter a colour display as an rgb
  43.      slider is dragged, etc.)
  44. */
  45.  
  46.  
  47.         /* Gap at each end of slider in OS coordinates */
  48. #define SLIDE_GAP 9
  49.         /* Minimum size slider can shrink to in OS coordinates
  50.            (should be equal to slider height) */
  51. #define SLIDE_MIN 12
  52.  
  53.  
  54.  
  55. extern int Icon_SetSlider(window_handle window,
  56.                           icon_handle baseicon, icon_handle slidericon,
  57.                           int sliderpos)
  58. /* Sets a slider icon-pair to the specified position (specify as a
  59.  * percentage). Values < 0 and > 1000 are clipped, and the value to which the
  60.  * slider has been set is returned.
  61.  */
  62. {
  63.   icon_handle      icon;
  64.   icon_createblock icreate;
  65.   register int     sliderwidth;
  66.  
  67.   if (sliderpos < 0)    sliderpos = 0;
  68.   if (sliderpos > 1000) sliderpos = 1000;
  69.  
  70.   Wimp_GetIconState(window, baseicon, &icreate.icondata);
  71.  
  72.   sliderwidth = (icreate.icondata.workarearect.max.x -
  73.                  icreate.icondata.workarearect.min.x) -
  74.                  (SLIDE_GAP * 2 + SLIDE_MIN);
  75.  
  76.   Wimp_GetIconState(window, slidericon, &icreate.icondata);
  77.   icreate.icondata.workarearect.max.x = icreate.icondata.workarearect.min.x +
  78.                                    (sliderpos * sliderwidth)/1001 + SLIDE_MIN;
  79.   icreate.window = window;
  80.   Wimp_DeleteIcon(window, slidericon);                 /* And resize icon... */
  81.   Wimp_CreateIcon(&icreate, &icon);
  82.   
  83.   {
  84.     window_redrawblock r;  /* Force window redraw to remove: getting smaller */
  85.  
  86.     r.window = window;
  87.     r.rect.min.x = icreate.icondata.workarearect.max.x + 4;
  88.     r.rect.max.x = icreate.icondata.workarearect.min.x + sliderwidth+SLIDE_MIN;
  89.     r.rect.min.y = icreate.icondata.workarearect.min.y;
  90.     r.rect.max.y = icreate.icondata.workarearect.max.y;
  91.     Wimp_ForceRedraw(&r);
  92.   }
  93.   Wimp_SetIconState(window, slidericon, 0, 0);         /* forceredraw slider */
  94.   return(sliderpos);
  95. }
  96.  
  97.  
  98.  
  99. extern int Icon_UpdateSlider(window_handle window,
  100.                              icon_handle baseicon, icon_handle slidericon,
  101.                              int lastpos)
  102. /* (call on null events while slider being dragged)
  103.  * Calculates a new slider percentage from the mouse pointer position.
  104.  * If this differs from lastpos, the slider is updated (by recreating the
  105.  * slidericon to the new length.
  106.  * returns the new slider position percentage value.
  107.  * NOTE: Slider update is achieved by DELETING and re-creating the slider
  108.  * icon. This relies upon no icons of a lower icon handle having been deleted!
  109.  */
  110. {
  111.   window_state     wstate;
  112.   icon_createblock icreate;
  113.   register int     sliderwidth, sliderpos;
  114.   mouse_block      ptr;
  115.   convert_block    convert;
  116.  
  117.   UNUSED( lastpos);
  118.   
  119.   Wimp_GetPointerInfo(&ptr);
  120.   Wimp_GetWindowState(window, &wstate);
  121.  
  122.   convert.screenrect = wstate.openblock.screenrect;
  123.   convert.scroll = wstate.openblock.scroll;
  124.  
  125.   Wimp_GetIconState(window, baseicon, &icreate.icondata);
  126.  
  127.   sliderwidth = (icreate.icondata.workarearect.max.x -
  128.                  icreate.icondata.workarearect.min.x) -
  129.                  (SLIDE_GAP * 2 + SLIDE_MIN);
  130.   sliderpos = Coord_XToWorkArea(ptr.pos.x, &convert) -
  131.               (icreate.icondata.workarearect.min.x + SLIDE_GAP + SLIDE_MIN);
  132.  
  133.   sliderpos = ((sliderpos * 1001) / sliderwidth);          /* get as 1..1000 */
  134.   return(Icon_SetSlider(window, baseicon, slidericon, sliderpos));
  135. }
  136.  
  137.  
  138.  
  139. extern int Icon_DragSlider(window_handle window,
  140.                            icon_handle baseicon, icon_handle slidericon)
  141. /* Initiates the drag operation on a slider. Call this when you get a click
  142.  * in either baseicon or slidericon.
  143.  * Returns the new percentage represented by the slider (remember this so
  144.  * you can pass it in to Icon_UpdateSlider to save unnecessary (flickery)
  145.  * update.)
  146.  * NOTE: It is up to you to turn on NULL events and remember that
  147.  * Icon_UpdateSlider must be called on each poll...
  148.  * An alternative is to make the 2 slider icons use button type ALWAYS, and
  149.  * check the mouse button state yourself to see whether a drag needs to be
  150.  * started/continued...
  151.  */
  152. {
  153.   convert_block convert;
  154.   window_state  state;
  155.   drag_block    dragdata;
  156.   icon_block    bicon, sicon;
  157.  
  158.   Wimp_GetIconState(window, baseicon, &bicon);
  159.   Wimp_GetIconState(window, slidericon, &sicon);
  160.  
  161.   Wimp_GetWindowState(window, &state);
  162.   convert.screenrect = state.openblock.screenrect;
  163.   convert.scroll     = state.openblock.scroll;
  164.  
  165.   dragdata.window    = window;
  166.   dragdata.type      = drag_INVISIBLE;
  167.   dragdata.screenrect= state.openblock.screenrect;   /* dragged box not used */
  168.   dragdata.parent.min.x = bicon.workarearect.min.x + SLIDE_GAP;
  169.   dragdata.parent.max.x = bicon.workarearect.max.x - SLIDE_GAP;
  170.   dragdata.parent.min.y = sicon.workarearect.min.y;
  171.   dragdata.parent.max.y = sicon.workarearect.max.y;
  172.  
  173.   Coord_RectToScreen(&dragdata.parent, &convert);
  174.  
  175.   Wimp_DragBox(&dragdata);
  176.   return(Icon_UpdateSlider(window, baseicon, slidericon, -1));
  177. }
  178.  
  179.  
  180.  
  181. extern int Icon_ReadSlider(window_handle window,
  182.                            icon_handle baseicon, icon_handle slidericon)
  183. /* Given a slider icon-pair, returns a percentage representing the state */
  184. {
  185.   icon_block   istate;
  186.   register int sliderwidth, sliderpos;
  187.  
  188.   Wimp_GetIconState(window, baseicon, &istate);
  189.   sliderwidth = (istate.workarearect.max.x - istate.workarearect.min.x) -
  190.                 (SLIDE_GAP * 2 + SLIDE_MIN);
  191.   Wimp_GetIconState(window, slidericon, &istate);
  192.   sliderpos = ((istate.workarearect.max.x - istate.workarearect.min.x)* 1001)
  193.                 / sliderwidth;
  194.  
  195.   if (sliderpos < 0)  sliderpos = 0;
  196.   if (sliderpos > 1000) sliderpos = 1000;
  197.  
  198.   return(sliderpos);
  199. }
  200.